import { Module } from 'vuex'
import { getFuncPermissions, getUserSystem } from '@/api/user'
import { keycloakConfig } from '@/config'
import { clientSetting } from '@/config/client-setting'

export interface MenuItem {
  path: string;
  name: string;
  key: string;
  icon?: string;
  activeIcon?: string;
  disabled?: boolean;
  requestType: 'internal' | 'external' | 'vForm' | 'microApp';
  jointRoute?: {
    metaTitle: string;
    request?: RequestProperties;
    form?: { formKey: string };
    micro?: MicroAppType;
  }
  children?: MenuItem[]
}
export interface MenuState {
  menuTree: MenuItem[];
  functions: string[];
  menuList: string[];
}

const useMenuData = (data: FuncPermissionsTreeRawItem[]): MenuItem[] => {
  if (Array.isArray(data)) {
    return data.map(v => {
      const children = useMenuData(v.children)
      const flag = v.data.request || v.data.form || v.data.micro
      const combinationRoute = {
        metaTitle: v.data.name,
        request: v.data.request,
        form: v.data.form,
        micro: v.data.micro
      }
      const microPath = v.data?.micro?.appPath
      const formPath = v.data.form ? `/form-preview/${v.data.form.formKey}` : ''
      return {
        path: microPath || formPath || v.data.path,
        name: v.data.name,
        key: v.data.key,
        icon: v.data.icon,
        activeIcon: v.data.activeIcon,
        requestType: v.data.requestType,
        jointRoute: flag ? combinationRoute : undefined,
        children: children.length ? children : undefined
      }
    })
  } else {
    return []
  }
}
const useFuncAndMenuList = (data: FuncPermissionsTreeRawItem[]) => {
  if (Array.isArray(data)) {
    const list: string[] = []
    const func: string[] = []
    data.forEach(v => {
      const child = v.children ? useFuncAndMenuList(v.children) : null
      const routePath = v.data?.micro?.appPath || v.data.path
      if (routePath) {
        list.push(routePath)
      }
      if (v.data.functions) {
        v.data.functions.forEach(k => {
          func.push(`${routePath}__${k.key}`)
        })
      }
      if (child) {
        list.push(...child.list)
        func.push(...child.func)
      }
    })
    return { list, func }
  } else {
    return { list: [], func: [] }
  }
}

// eslint-disable-next-line
const menu: Module<MenuState, any> = {
  namespaced: true,
  state: () => ({
    menuTree: [],
    functions: [],
    menuList: []
  }),
  getters: {
    getMenuTree(state) {
      return state.menuTree
    },
    getFunctions(state) {
      return state.functions
    },
    getMenuList(state) {
      return state.menuList
    }
  },
  mutations: {
    SET_MENU_DATA(state, payload) {
      state.menuTree = payload
    },
    SET_FUNCTIONS(state, payload) {
      state.functions = payload
    },
    SET_MENU_LIST(state, payload) {
      state.menuList = payload
    }
  },
  actions: {
    getMenu({ commit, rootState }) {
      return new Promise((resolve, reject) => {
        const query = { userName: rootState.user?.userInfo?.userName, sysFlag: keycloakConfig.clientId }
        getFuncPermissions(query).then(res => {
          const value = res.data?.children
          if (value) {
            const menu = useMenuData(value)
            const { func, list } = useFuncAndMenuList(value)
            commit('SET_MENU_DATA', menu)
            commit('SET_FUNCTIONS', func)
            commit('SET_MENU_LIST', list)
            resolve(menu)
          } else {
            reject(res.data)
          }
        }).catch(reject)
      })
    },
    resetMenu({ commit }) {
      commit('SET_MENU_DATA', [])
      commit('SET_FUNCTIONS', [])
      commit('SET_MENU_LIST', [])
    },
    getTopMenu ({ commit, rootState }) {
      return new Promise((resolve, reject) => {
        const userName = rootState.user?.userInfo?.userName
        getUserSystem(userName).then(res => {
          const response = res.data
          if (response) {
            const topMenu = response.map((v: { key: string; value: string }) => {
              return {
                key: v.key,
                name: v.value,
                path: v.key
              }
            })
            commit('SET_HEADER_MENU', topMenu)
            resolve(topMenu)
          } else {
            reject(res.data)
          }
        }).catch(reject)
      })
    }
  }
}


export default menu
